﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.IO;
using System.Xml.Serialization;
using System.Xml.Linq;
using System.Reflection;

namespace Mindfor.Error
{
	/// <summary>
	/// Provides functions to submit exceptions to Mindfor server.
	/// </summary>
	public static class ErrorProxy
	{
		static Uri s_submitUri = new Uri("http://www.mindfor.ru/errors/submit", UriKind.Absolute);
		//static Uri s_submitUri = new Uri("http://zorrovirtual:7460/errors/submit", UriKind.Absolute);

		/// <summary>
		/// Submits application exception to server. Exception is thrown if connection problem occures.
		/// </summary>
		/// <param name="applicationId">Unique application id that is registered at Mindfor server.</param>
		/// <param name="version">Version of running application (from 1 to 20 characters). If null or empty then entry assembly version is taken.</param>
		/// <param name="ex">Exception occured.</param>
		public static SubmitResult Submit(Guid applicationId, string version, Exception ex)
		{
			// get version
			if (version == "")
				version = null;
			if (version == null)
			{
				Assembly entryAsm = Assembly.GetEntryAssembly();
				if (entryAsm != null)
					version = entryAsm.GetName().Version.ToString();
			}

			// generate colletion
			ErrorData data = new ErrorData(applicationId);
			data.ApplicationVersion = version;
			while (ex != null)
			{
				data.Exceptions.Add(new ExceptionInfo(ex));
				ex = ex.InnerException;
			}
			
			// send request
			HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(s_submitUri);
			request.ContentType = "text/xml";
			request.Method = "POST";
			using (Stream s = request.GetRequestStream())
			{
				XmlSerializer serializer = new XmlSerializer(typeof(ErrorData));
				serializer.Serialize(s, data);
			}

			// get response
			HttpWebResponse response = (HttpWebResponse)request.GetResponse();
			using (Stream s = response.GetResponseStream())
			{
				try
				{
					XDocument doc = XDocument.Load(s);
					return (SubmitResult)Enum.Parse(typeof(SubmitResult), doc.Root.Value);
				}
				catch
				{
					return SubmitResult.ServerError;
				}
			}
		}

		/// <summary>
		/// Submits application exception to server. Application version is taken from entry assembly version.
		/// Exception is thrown if connection problem occures.
		/// </summary>
		/// <param name="applicationId">Unique application id that is registered at Mindfor server.</param>
		/// <param name="ex">Exception occured.</param>
		public static SubmitResult Submit(Guid applicationId, Exception ex)
		{
			return Submit(applicationId, null, ex);
		}

		/// <summary>
		/// Submits application exception to server. ClientError is returned if connection problem occures.
		/// </summary>
		/// <param name="applicationId">Unique application id that is registered at Mindfor server.</param>
		/// <param name="version">Version of running application (from 1 to 20 characters). If null or empty then entry assembly version is taken.</param>
		/// <param name="ex">Exception occured.</param>
		public static SubmitResult SubmitSafe(Guid applicationId, string version, Exception ex)
		{
			try
			{
				return Submit(applicationId, version, ex);
			}
			catch
			{
				return SubmitResult.ClientError;
			}
		}

		/// <summary>
		/// Submits application exception to server. Application version is taken from entry assembly version.
		/// ClientError is returned if connection problem occures.
		/// </summary>
		/// <param name="applicationId">Unique application id that is registered at Mindfor server.</param>
		/// <param name="ex">Exception occured.</param>
		public static SubmitResult SubmitSafe(Guid applicationId, Exception ex)
		{
			return SubmitSafe(applicationId, null, ex);
		}
	}
}
